﻿using Bluetooth_Fan.BluetoothFan.Classes;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Runtime.InteropServices;
using System.Text;

namespace Bluetooth_Fan.Classes
{
    public enum SYS_USER_COMM_Enum      //命令集 枚举
    {
        /// <summary>
        ///保留命令
        /// </summary>
        SET_Reserve = 0,
        /// <summary>
        /// 设置电机分段转速
        /// </summary>
        SET_MOTO_PWM_Section_COMM = 0X01,
        /// <summary>
        /// 设置电机PWM 值
        /// </summary>
        SET_MOTO_PWM_COMM = 0X02,
        /// <summary>
        /// 设置电机定时功能
        /// </summary>
        SET_MOTO_RUN_TIME_COMM = 0X03,
        /// <summary>
        /// 设置电机正反转
        /// </summary>
        SET_MOTO_Direction_COMM = 0X04,

        //请求设备参数 --------------
        /// <summary>
        ///上报设备运行状态   PWM值  运行时间   应答
        /// </summary>
        Rep_SYS_RUN_STA = 0XF1,
        /// <summary>
        /// 上报设备运行参数    ADC采集的数据  应答
        /// </summary>
        Rep_SYS_State = 0XF2,
        /// <summary>
        /// 上报及请求固件版本
        /// </summary>
        Rep_SYS_VER = 0XFF,
    }

    public enum CmmErrCode
    {
        ErrOk,
        ErrLength,
        ErrCmm,
        ErrHeah,
        ErrData,
        ErrCRC,
    }

    /// <summary>
    /// 设备控制结构体
    /// </summary>
    /// 
    public class CDeviceControlCMM : IMessage
    {
        internal static readonly byte[] Head = new byte[] { 0XAA, 0X55 };

        /// <summary>
        /// 命令
        /// </summary>
        private SYS_USER_COMM_Enum _Command;
        public SYS_USER_COMM_Enum Command { get { return _Command; } }

        /// <summary>
        /// 数据段
        /// </summary>
        private byte[] _parameters;
        public byte[] parameters { get { return _parameters; } }

        /// <summary>
        /// 
        /// </summary>
        /// <param name="data">最后一个字节为CRC</param>
        /// <returns></returns>
        public static byte GetCrc(byte[] data)
        {
            byte crc = 0;
            for (int i = 0; i < (data.Length - 1); i++)
            {
                crc += data[i];
            }
            crc = (byte)(0 - crc);
            return crc;
        }

        /// <summary>
        /// 接口的实现   当前用于发送的命令
        /// </summary>
        public byte[] MessageData
        {
            get
            {
                int length = Head.Length + 1 + 1 + 1;
                byte[] Databuff;
                if (_parameters != null)
                {
                    length += _parameters.Length;
                    Databuff = new byte[length];
                    Databuff[3] = (byte)_parameters.Length;
                    Array.Copy(_parameters, 0, Databuff, 4, _parameters.Length);
                }
                else
                {
                    Databuff = new byte[length];
                    Databuff[3] = 0;
                }

                Array.Copy(Head, Databuff, Head.Length); //拷贝数据头
                Databuff[2] = (byte)_Command;   //命令
                //计算CRC ------------------------
                Databuff[length - 1] = GetCrc(Databuff);
                return Databuff;
            }
        }
        public CDeviceControlCMM(SYS_USER_COMM_Enum command)
        {
            _Command = command;
        }
        public CDeviceControlCMM(SYS_USER_COMM_Enum command, byte[] parameters)
            : this(command)
        {
            _parameters = parameters;
        }


        #region 公有静态方法

        public static CmmErrCode IsDeviceControlCMM(byte[] RecBuff, ref byte[] CommData, ref int len)
        {
            if (RecBuff.Length < 5)
            {
                len = RecBuff.Length;
                return CmmErrCode.ErrLength;
            }
            if ((RecBuff[0] != Head[0]) || (RecBuff[1] != Head[1]))
            {
                len = 2;
                return CmmErrCode.ErrHeah;
            }
            if (Enum.IsDefined(typeof(SYS_USER_COMM_Enum), (Int32)RecBuff[2]) == false)
            {
                len = 3;
                return CmmErrCode.ErrCmm;
            }
            len = 5 + RecBuff[3];  //得到此帧的数据长度
            if (RecBuff.Length < len)
            {
                len = RecBuff.Length;
                return CmmErrCode.ErrLength;
            }
            byte[] Buff = new byte[len];
            Array.Copy(RecBuff, Buff, Buff.Length);  //拷贝此帧的数据
            if (Buff[Buff.Length - 1] != GetCrc(Buff))
            {
                len = Buff.Length;
                return CmmErrCode.ErrCRC;
            }
            //到此 此数据帧解析完毕  拷贝 命令 +数据域长度 +数据
            CommData = new byte[Buff.Length - 3];
            Array.Copy(Buff, 2, CommData, 0, CommData.Length);
            return CmmErrCode.ErrOk;
        }
        #endregion

    }
}
